<!DOCTYPE html>
<html>

<head lang="en">
    <meta charset="utf-8" />
    <title>BIP39 - Mnemonic Code</title>
    <link rel="stylesheet" href="css/bootstrap-3.3.7.css">
    <link rel="stylesheet" href="css/app.css">
    <meta content="Mnemonic code for generating deterministic keys" name="description" />
    <meta content="width=device-width, initial-scale=1.0" name="viewport" />
    <meta content="bitcoin mnemonic converter" name="description" />
    <meta content="Ian Coleman" name="author" />
    <link type="image/x-icon" rel="icon"
        href="" />
</head>

<body>
    <div class="container">
        <h1 class="text-center">Mnemonic Code Converter</h1>
        <p class="version">v0.3.8s</p>
        <hr>
        <div class="row">
            <div class="col-md-12">
                <h2>Mnemonic</h2>
                <form class="form-horizontal" role="form">
                    <div class="form-group">
                        <div class="col-sm-2"></div>
                        <div class="col-sm-10">
                            <p>You can enter an existing BIP39 mnemonic, or generate a new random one. Typing your own
                                twelve words will probably not work how you expect, since the words require a particular
                                structure (the last word is a checksum).</p>
                            <p>
                                For more info see the
                                <a href="https://github.com/bitcoin/bips/blob/master/bip-0039.mediawiki"
                                    target="_blank">BIP39 spec</a>.
                            </p>
                        </div>
                    </div>
                    <div class="form-group generate-container">
                        <label class="col-sm-2 control-label"></label>
                        <div class="col-sm-10">
                            <div class="form-inline">
                                <div class="input-group-inline">
                                    <span>Generate a random mnemonic, or enter your own below</span>:
                                    <button class="btn generate">Generate</button>
                                    <select id="strength" class="strength form-control" disabled="disabled">
                                        <option value="12" selected>12</option>
                                    </select>
                                    <span>words</span>.
                                    <p class="warning help-block hidden">
                                        <span class="text-danger">
                                            Mnemonics with less than 12 words have low entropy and may be guessed by an
                                            attacker.
                                        </span>
                                    </p>
                                </div>
                            </div>
                        </div>
                    </div>
                    <div class="entropy-container hidden">
                        <div class="form-group text-danger">
                            <label class="col-sm-2 control-label">Warning</label>
                            <div class="col-sm-10 form-control-static">
                                <span>Entropy is an advanced feature. Your mnemonic may be insecure if this feature is
                                    used incorrectly.</span>
                                <a href="#entropy-notes">Read more</a>
                            </div>
                        </div>
                        <div class="form-group">
                            <label for="entropy" class="col-sm-2 control-label">Entropy</label>
                            <div class="col-sm-7">
                                <textarea id="entropy" rows="2" class="entropy private-data form-control"
                                    placeholder="Accepts either binary, base 6, 6-sided dice, base 10, hexadecimal or cards"
                                    disabled="disabled"></textarea>
                                <div class="row filter-warning text-danger hidden">
                                    <p class="col-sm-12">
                                        <strong>
                                            Some characters have been discarded
                                        </strong>
                                    </p>
                                </div>
                                <div class="row">
                                    <label class="col-sm-3 control-label"><span class="more-info"
                                            title="Based on estimates from zxcvbn using Filtered Entropy">Time To
                                            Crack</span></label>
                                    <div class="crack-time col-sm-3 form-control-static"></div>
                                    <label class="col-sm-3 control-label">Event Count</label>
                                    <div class="event-count col-sm-3 form-control-static"></div>
                                </div>
                                <div class="row">
                                    <label class="col-sm-3 control-label">Entropy Type</label>
                                    <div class="type col-sm-3 form-control-static"></div>
                                    <label class="col-sm-3 control-label">Bits Per Event</label>
                                    <div class="bits-per-event col-sm-3 form-control-static"></div>
                                </div>
                                <div class="row">
                                    <label class="col-sm-3 control-label">Raw Entropy Words</label>
                                    <div class="word-count col-sm-3 form-control-static"></div>
                                    <label class="col-sm-3 control-label"><span class="more-info"
                                            title="Total bits of entropy may be less than indicated if any entropy event uses a weak source.">Total
                                            Bits</span></label>
                                    <div class="bits col-sm-3 form-control-static"></div>
                                </div>
                                <label class="col-sm-3 control-label">Filtered Entropy</label>
                                <div class="filtered private-data col-sm-9 form-control-static"></div>
                                <label class="col-sm-3 control-label">Raw Binary</label>
                                <div class="binary private-data col-sm-9 form-control-static"></div>
                                <label class="col-sm-3 control-label">Binary Checksum</label>
                                <div class="checksum private-data col-sm-9 form-control-static">&nbsp;</div>
                                <label class="col-sm-3 control-label">Word Indexes</label>
                                <div class="word-indexes private-data col-sm-9 form-control-static">&nbsp;</div>
                                <label class="col-sm-3 control-label">Mnemonic Length</label>
                                <div class="col-sm-9">
                                    <select class="mnemonic-length form-control" disabled="disabled">
                                        <option value="raw">Use Raw Entropy (3 words per 32 bits)</option>
                                        <option value="12" selected>12 <span>Words</span></option>
                                        <option value="15">15 <span>Words</span></option>
                                        <option value="18">18 <span>Words</span></option>
                                        <option value="21">21 <span>Words</span></option>
                                        <option value="24">24 <span>Words</span></option>
                                    </select>
                                    <p class="weak-entropy-override-warning hidden">
                                        <span class="text-danger">
                                            The mnemonic will appear more secure than it really is.
                                        </span>
                                    </p>
                                </div>
                            </div>
                            <div class="col-sm-3">
                                <p>Valid entropy values include:</p>
                                <ul>
                                    <li><strong>Binary</strong> [0-1]<br>101010011</li>
                                    <li><strong>Base 6</strong> [0-5]<br>123434014</li>
                                    <li><strong>Dice</strong> [1-6]<br>62535634</li>
                                    <li><strong>Base 10</strong> [0-9]<br>90834528</li>
                                    <li><strong>Hex</strong> [0-9A-F]<br>4187a8bfd9</li>
                                    <li><strong>Card</strong> [A2-9TJQK][CDHS]<br>ahqs9dtc</li>
                                </ul>
                            </div>
                        </div>
                    </div>
                    <div class="form-group">
                        <div class="col-sm-2"></div>
                        <div class="col-sm-10 checkbox">
                            <label>
                                <input type="checkbox" class="use-entropy">
                                <span>Show entropy details</span>
                            </label>
                        </div>
                    </div>
                    <div class="form-group">
                        <div class="col-sm-2"></div>
                        <div class="col-sm-10 checkbox">
                            <label>
                                <input type="checkbox" class="privacy-screen-toggle">
                                <span>Hide all private info</span>
                            </label>
                        </div>
                    </div>
                    <div class="form-group">
                        <label class="col-sm-2 control-label">Mnemonic Language</label>
                        <div class="col-sm-10 languages">
                            <div class="form-control no-border">
                                <a href="#english" id="default-lang">English</a>
                            </div>
                        </div>
                    </div>
                    <div class="form-group">
                        <label for="phrase" class="col-sm-2 control-label">BIP39 Mnemonic</label>
                        <div class="col-sm-10">
                            <textarea id="phrase" class="phrase private-data form-control" data-show-qr></textarea>
                        </div>
                    </div>
                    <div class="form-group">
                        <label for="passphrase" class="col-sm-2 control-label">BIP39 Passphrase (optional)</label>
                        <div class="col-sm-10">
                            <textarea id="passphrase" class="passphrase private-data form-control"
                                disabled="disabled"></textarea>
                        </div>
                    </div>
                    <div class="form-group">
                        <label for="seed" class="col-sm-2 control-label">BIP39 Seed</label>
                        <div class="col-sm-10">
                            <textarea id="seed" class="seed private-data form-control" readonly="readonly"
                                data-show-qr></textarea>
                        </div>
                    </div>
                    <div class="form-group">
                        <label for="network-phrase" class="col-sm-2 control-label">Coin</label>
                        <div class="col-sm-10">
                            <select id="network-phrase" class="network form-control" disabled="disabled">
                                <!-- populated by javascript -->
                            </select>
                        </div>
                    </div>
                    <div class="form-group">
                        <label for="root-key" class="col-sm-2 control-label">BIP32 Root Key</label>
                        <div class="col-sm-10">
                            <textarea id="root-key" disabled="disabled" class="root-key private-data form-control"
                                data-show-qr></textarea>
                        </div>
                    </div>
                    <div class="form-group litecoin-ltub-container hidden">
                        <label for="litecoin-use-ltub" class="col-sm-2 control-label">Prefixes</label>
                        <div class="col-sm-10 checkbox">
                            <label>
                                <input type="checkbox" id="litecoin-use-ltub" class="litecoin-use-ltub"
                                    checked="checked">
                                Use <code>Ltpv / Ltub</code> instead of <code>xprv / xpub</code>
                            </label>
                        </div>
                    </div>
                </form>
            </div>
        </div>

        <hr>

        <div class="row">
            <div class="col-md-12">
                <h2>Derivation Path</h2>
                <ul class="derivation-type nav nav-tabs" role="tablist">
                    <li id="bip32-tab" class="active">
                        <a href="#bip32" role="tab" data-toggle="tab">BIP32</a>
                    </li>
                </ul>
                <div class="derivation-type tab-content">
                    <div id="bip32" class="tab-pane active">
                        <form class="form-horizontal" role="form">
                            <br>
                            <div class="col-sm-2"></div>
                            <div class="col-sm-10">
                                <p>
                                    For more info see the
                                    <a href="https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki"
                                        target="_blank">BIP32 spec</a>
                                </p>
                            </div>
                            <div class="form-group">
                                <label for="bip32-client" class="col-sm-2 control-label">Client</label>
                                <div class="col-sm-10">
                                    <select id="bip32-client" class="client form-control" disabled="disabled">
                                        <option value="custom">Custom derivation path</option>
                                        <!-- populated by javascript -->
                                    </select>
                                </div>
                            </div>
                            <div class="form-group">
                                <label for="bip32-path" class="col-sm-2 control-label">BIP32 Derivation Path</label>
                                <div class="col-sm-10">
                                    <input id="bip32-path" type="text" class="path form-control" value="m/0"
                                        disabled="disabled">
                                </div>
                            </div>
                            <div class="form-group">
                                <div class="col-sm-2"></div>
                                <label class="col-sm-10">
                                    <input class="hardened-addresses" type="checkbox" disabled="disabled">
                                    <span>Use hardened addresses</span>
                                </label>
                            </div>
                            <div class="form-group">
                                <label for="core-path" class="col-sm-2 control-label">Bitcoin Core</label>
                                <div class="col-sm-10">
                                    <p class="form-control no-border">
                                        Use path <code>m/0'/0'</code> with hardened addresses.
                                    </p>
                                    <p class="form-control no-border">
                                        For more info see the
                                        <a href="https://github.com/bitcoin/bitcoin/pull/8035" target="_blank">Bitcoin
                                            Core BIP32 implementation</a>
                                    </p>
                                </div>
                            </div>
                            <div class="form-group">
                                <label for="core-path" class="col-sm-2 control-label">Multibit</label>
                                <div class="col-sm-10">
                                    <p class="form-control no-border">
                                        <span>Use path <code>m/0'/0</code>.</span>
                                    </p>
                                    <p class="form-control no-border">
                                        <span>For more info see</span>
                                        <a href="https://multibit.org/" target="_blank">MultiBit HD</a>
                                    </p>
                                </div>
                            </div>
                            <div class="form-group">
                                <label class="col-sm-2 control-label">Block Explorers</label>
                                <div class="col-sm-10">
                                    <p class="form-control no-border">
                                        <span>Use path <code>m/44'/0'/0'</code>.</span>
                                        <span>Only enter the <code>xpub</code> extended key into block explorer search
                                            fields, never the <code>xprv</code> key.</span>
                                    </p>
                                    <p class="form-control no-border">
                                        <span>Can be used with</span>:
                                        <a href="https://blockchain.info/" target="_blank">blockchain.info</a>
                                    </p>
                                </div>
                            </div>
                        </form>
                    </div>
                </div>
                <form class="form-horizontal" role="form">
                    <div class="form-group">
                        <label for="extended-priv-key" class="col-sm-2 control-label">BIP32 Extended Private Key</label>
                        <div class="col-sm-10">
                            <textarea id="extended-priv-key" class="extended-priv-key private-data form-control"
                                readonly="readonly" data-show-qr></textarea>
                        </div>
                    </div>
                    <div class="form-group">
                        <label for="extended-pub-key" class="col-sm-2 control-label">BIP32 Extended Public Key</label>
                        <div class="col-sm-10">
                            <textarea id="extended-pub-key" class="extended-pub-key form-control" readonly="readonly"
                                data-show-qr></textarea>
                        </div>
                    </div>
                </form>
            </div>
        </div>

        <hr>

        <div class="row">
            <div class="col-md-12">
                <h2>Derived Addresses</h2>
                <p>Note these addresses are derived from the BIP32 Extended Key</p>
            </div>
            <div class="col-md-12 bch-addr-type-container hidden">
                <div class="radio">
                    <label>
                        <input type="radio" value="cashaddr" name="bch-addr-type" class="use-bch-cashaddr-addresses"
                            checked="checked">
                        <span>Use CashAddr addresses for Bitcoin Cash (ie starting with 'q' instead of '1')</span>
                    </label>
                </div>
                <div class="radio">
                    <label>
                        <input type="radio" value="bitpay" name="bch-addr-type" class="use-bch-bitpay-addresses">
                        <span>Use BitPay-style addresses for Bitcoin Cash (ie starting with 'C' instead of '1')</span>
                    </label>
                </div>
                <div class="radio">
                    <label>
                        <input type="radio" value="legacy" name="bch-addr-type" class="use-bch-legacy-addresses">
                        <span>Use legacy addresses for Bitcoin Cash (ie starting with '1')</span>
                    </label>
                </div>
            </div>
            <div class="col-md-12">
                <div class="checkbox">
                    <label>
                        <input type="checkbox" class="use-bip38" disabled="disabled">
                        <span>Encrypt private keys using BIP38 and this password:</span>
                    </label>
                    <input class="bip38-password private-data" disabled="disabled">
                    <span>Enabling BIP38 means each key will take several minutes to generate.</span>
                </div>
            </div>
            <div class="col-md-12">
                <div class="checkbox">
                    <label>
                        <input type="checkbox" class="compressed" checked>
                        <span>compressed</span>
                    </label>
                </div>
            </div>
            <ul class="addresses-type nav nav-tabs" role="tablist">
                <li id="table-tab" class="active">
                    <a href="#table" role="tab" data-toggle="tab">Table</a>
                </li>
                <li id="csv-tab">
                    <a href="#csv" role="tab" data-toggle="tab">CSV</a>
                </li>
            </ul>
            <div class="addresses-type tab-content">
                <div id="table" class="tab-pane active">
                    <div class="col-md-12">
                        <table class="table table-striped">
                            <thead>
                                <th>
                                    <div class="input-group">
                                        <span>Path</span>&nbsp;&nbsp;
                                        <button class="index-toggle">Toggle</button>
                                    </div>
                                </th>
                                <th>
                                    <div class="input-group">
                                        <span>Address</span>&nbsp;&nbsp;
                                        <button class="address-toggle">Toggle</button>
                                    </div>
                                </th>
                                <th>
                                    <div class="input-group">
                                        <span>Public Key</span>&nbsp;&nbsp;
                                        <button class="public-key-toggle">Toggle</button>
                                    </div>
                                </th>
                                <th>
                                    <div class="input-group">
                                        <span>Private Key</span>&nbsp;&nbsp;
                                        <button class="private-key-toggle">Toggle</button>
                                    </div>
                                </th>
                            </thead>
                            <tbody class="addresses monospace">
                                <tr>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                </tr>
                                <tr>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                </tr>
                                <tr>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                </tr>
                                <tr>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                </tr>
                                <tr>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                    <td>&nbsp;</td>
                                </tr>
                            </tbody>
                        </table>
                    </div>
                </div>
                <div id="csv" class="tab-pane">
                    <div class="col-md-12">
                        <textarea class="csv form-control" rows="25" readonly></textarea>
                    </div>
                </div>
            </div>
        </div>
        <span>Show</span>
        <input type="number" class="rows-to-add" value="1" disabled="disabled">
        <button class="more">more rows</button>
        <span>starting from index</span>
        <input type="number" class="more-rows-start-index" disabled="disabled">
        <span>(leave blank to generate from next index)</span>
        <hr>

        <div class="qr-container hidden">
            <div class="qr-hint bg-primary hidden">Click field to hide QR</div>
            <div class="qr-hint bg-primary">Click field to show QR</div>
            <div class="qr-hider hidden">
                <div class="qr-image"></div>
                <div class="qr-warning bg-primary">Caution: Scanner may keep history</div>
            </div>
        </div>

        <div class="feedback-container">
            <div class="feedback">Loading...</div>
        </div>
    </div>
    <script type="text/template" id="address-row-template">
            <tr>
                <td class="index"><span></span></td>
                <td class="address"><span data-show-qr></span></td>
                <td class="pubkey"><span data-show-qr></span></td>
                <td class="privkey private-data"><span data-show-qr></span></td>
            </tr>
        </script>

    <script src="js/polyfill.es6.js"></script>
    <script src="js/basex.js"></script>
    <script src="js/unorm.js"></script>
    <script src="js/jquery-3.2.1.js"></script>
    <script src="js/bootstrap-3.3.7.js"></script>
    <script src="js/levenshtein.js"></script>
    <script src="js/kjua-0.1.1.min.js"></script>
    <script src="js/bitcoinjs-3.3.2.js"></script>
    <script src="js/bitcoinjs-extensions.js"></script>
    <script src="js/bitcoinjs-bip38-2.0.2.js"></script>
    <script src="js/segwit-parameters.js"></script>
    <script src="js/ethereumjs-util.js"></script>
    <script src="js/ripple-util.js"></script>
    <script src="js/bchaddrjs-0.2.1.js"></script>
    <script src="js/sjcl-bip39.js"></script>
    <script src="js/wordlist_english.js"></script>
    <script src="js/jsbip39.js"></script>
    <script src="js/biginteger.js"></script>
    <script src="js/zxcvbn.js"></script>
    <script src="js/entropy.js"></script>
    <script src="js/index.js"></script>
    <script src="js/cal.js"></script>
    <script src="js/crypto-js.js"></script>
    <script>
        // pk2Keystore("L4JQLkMFWbTG9dR8QDnfcHkNGaT2ipoVtGYLrJREFCZXwRkWPhsF","123454536f667445454d537973576562");
        // pk2Keystore('L3askAPoeZHBnRa63kQrnDuV7YhyrpGZCMUhFhufTiwj21sXT1LN', '222222');
        // let ciphertext = "U2FsdGVkX1/OluYnMPYCTQsSM6+VvGZj2FM1lYEk4NK0zg9lbynhqxflPPLfRm6+6k8beGJjLsSY3tAbCbmPdtgaLRz9JJFtVx2BMsXicboAshpQcELIyBNQkmLYsrkKGovTqg3VMbKeb1+dlcKaLynq/+McelC0nf9qhgCOYKw2ZZcBjKNfyK6GAsI3eoD7+GctoxjfsDe4V1pVDrk4aVdreSoLvshRVXN7aWwJH/YAdThgRtnYoeyvrc2Ly3P17+tMxlIy74//xZzCmKV05dVSLbipTuoDCzOKa+KMpIJbicdcyZRUv57kLfGMuGPxOFA5gSQwCemsbk1+slYP4jhNYqj/pKj/du+NCoyo1TorOgLLk1pE90eBnwGhzIs3UnVUfr235ceXpp4eR6a4QiKYuuR3v7FXKq1c9D8LDdpSLVy/Rn7yKZo+ysM6VBbPvaDGFvx/I5BCKUIZgz+KEl8/KvXvl/LY2L+Sr/e3iqNBBkzzNpiabNBzij3PT5IW+si+FujOapHtVbG25YuPVgQc20Lxe5supmOM5L40qxQ=";
        // importWalletByKeystore(ciphertext, "222222");
        // importWallet("auto long orchard robot acquire dose picnic tourist toy subject waste also");
        // importWalletByWIF("KwhnM3iFqc1HQJRjUVv38qUcGUibCxHCd2Kbu8RfgS1v62Sq4yV1");
        // let message = 'a secret message';
        // let wif = 'L4JQLkMFWbTG9dR8QDnfcHkNGaT2ipoVtGYLrJREFCZXwRkWPhsF';
        // sign(message, wif);
        function sign(message, wif) {
            try {
                let hash = bitcoinjs.bitcoin.crypto.sha256(message);
                let keyPair = bitcoinjs.bitcoin.ECPair.fromWIF(wif);
                let signature = keyPair.sign(hash).toDER();
                postMsg(0, { signature: signature.toString('hex') });
            } catch (err) {
                postMsg(1);
            }
        }
        function buf2hex(buffer) { // buffer is an ArrayBuffer
            return Array.prototype.map.call(new Uint8Array(buffer), x => ('00' + x.toString(16)).slice(-2)).join('');
        }
        function hextoString(hex) {
            var arr = hex.split("")
            var out = ""
            for (var i = 0; i < arr.length / 2; i++) {
                var tmp = "0x" + arr[i * 2] + arr[i * 2 + 1]
                var charValue = String.fromCharCode(tmp);
                out += charValue
            }
            return out
        }
        function string2Hex(str) {
            var val = "";
            for (var i = 0; i < str.length; i++) {
                if (val == "")
                    val = str.charCodeAt(i).toString(16);
                else
                    val += str.charCodeAt(i).toString(16);
            }
            val += "0a"
            return val
        }
        function importWalletByKeystore(keystore, pwd) {
            let pk = keystore2pk(keystore, pwd);
            importWalletByWIF(pk);
        }
        function pk2Keystore(pk, pwd) {
            try {
                let iv = CryptoJS.lib.WordArray.random(128 / 8).toString(CryptoJS.enc.Hex);//随机生成长度为32的16进制字符串。IV称为初始向量，不同的IV加密后的字符串是不同的，加密和解密需要相同的IV。
                // iv = CryptoJS.enc.Utf8.parse(pwd.toString());
                let encryptJSON = {
                    iv: iv,
                    mode: "CBC",
                    blockSize: 4,
                    padding: "PkCS7",
                    ciphertext: aesEncrypt(pk, pwd, iv),
                };
                let encryptJSONstr = JSON.stringify(encryptJSON);
                // console.log("encryptJSONstr: " + encryptJSONstr);
                let ciphertext = aesEncrypt(encryptJSONstr, pwd, iv);
                let packageJSON = {
                    version: 1,
                    ciphertext: ciphertext,
                    iv: iv
                }
                let oriIv = CryptoJS.MD5(pwd).toString().toUpperCase().substr(0, 32).toString(CryptoJS.enc.Hex)
                let packageJSONstr = aesEncrypt(JSON.stringify(packageJSON), pwd, oriIv);
                // console.log("packageJSONstr: " + packageJSONstr);
                let data = {
                    ciphertext: packageJSONstr
                }
                postMsg(0, data);
            } catch (err) {
                postMsg(1);
            }
        }

        function keystore2pk(keystore, pwd) {
            try {
                let oriIv = CryptoJS.MD5(pwd).toString().toUpperCase().substr(0, 32).toString(CryptoJS.enc.Hex)
                let packageJson = aesDecrypt(keystore, pwd, oriIv);
                packageJson = JSON.parse(packageJson);

                // console.log("packageJson: " + JSON.stringify(packageJson));
                // packageJson = aesDecrypt(packageJson.ciphertext, pwd, packageJson.iv); 
                packageJson = aesDecrypt(packageJson.ciphertext, pwd, packageJson.iv);
                packageJson = JSON.parse(packageJson);
                // console.log("packageJson: " + JSON.stringify(packageJson));
                let pk = aesDecrypt(packageJson.ciphertext, pwd, packageJson.iv);
                return pk;
            } catch (err) {
                postMsg(1);
            }
        }

        function aesEncrypt(message, key, iv) {
            var iv = CryptoJS.enc.Utf8.parse(iv);
            var ciphertext = CryptoJS.AES.encrypt(message, key, {
                iv: iv,
                mode: CryptoJS.mode.CBC,
                blockSize: 4,
                padding: CryptoJS.pad.Pkcs7
            });
            // return ciphertext;//密码对象(Obejct类型，非WordArray类型)，Base64编码。
            return ciphertext.toString();//密码对象的Base64字符串
        }
        //** 解密 **
        //var plaintext  = CryptoJS.AES.decrypt(ciphertext, key, cfg);
        //params: 注意参数ciphertext 必须为 Base64编码的对象或者字符串。
        function aesDecrypt(ciphertext, key, iv) {
            var iv = CryptoJS.enc.Utf8.parse(iv);
            var decrypted = CryptoJS.AES.decrypt(ciphertext, key, {
                iv: iv,
                mode: CryptoJS.mode.CBC,
                blockSize: 4,
                padding: CryptoJS.pad.Pkcs7
            });
            return decrypted.toString(CryptoJS.enc.Utf8);//WordArray对象转utf8字符串
        }
        function createWallet() {
            try {
                document.getElementById("default-lang").click();
            } catch (error) {
                postMsg(1);
            }
        }
        function importWallet(bip39MnemonicWords) {
            try {
                document.getElementById("phrase").value = bip39MnemonicWords;
                document.getElementById("default-lang").click();
            } catch (error) {
                postMsg(1);
            }
        }
        function importWalletByWIF(wif) {
            try {
                let newECPair = bitcoinjs.bitcoin.ECPair.fromWIF(wif);
                let walletInfo = {
                    address: newECPair.getAddress(),
                    compressedPubkey: newECPair.getPublicKeyBuffer().toString('hex'),
                    compressedPrivkey: wif
                }
                let returnJSON = {
                    code: 0,
                    errorMsg: "",
                    data: {
                        walletInfo: walletInfo
                    }
                }
                // return (JSON.stringify(returnJSON));
                let data = {
                    address: newECPair.getAddress(),
                    pubkey: newECPair.getPublicKeyBuffer().toString('hex'),
                    privkey: wif
                }
                postMsg(0, data);
            } catch (err) {
                postMsg(1);
            }
        }
        function postMsg(errCode, data = {}) {
            let walletInfo = {
                address: data.address || '',
                compressedPubkey: data.pubkey || '',
                compressedPrivkey: data.privkey || '',
                mnemonicWords: document.getElementById("phrase").value || '',
                ciphertext: data.ciphertext || '',
                signature: data.signature || ''
            }
            let returnJSON = {
                errCode: errCode,
                errorMsg: "",
                data: {
                    walletInfo: walletInfo
                }
            }
            var agent = navigator.userAgent.toLowerCase();
            var android = agent.indexOf("android");
            var iphone = agent.indexOf("iphone");
            var ipad = agent.indexOf("ipad");
            // console.log("postMsg: " + JSON.stringify(returnJSON));
            if (android != -1) {
                Android.walletInfoCB(JSON.stringify(returnJSON, "/n", null));
            } else if (iphone != -1 || ipad != -1) {
                window.webkit.messageHandlers.walletInfoCB.postMessage(JSON.stringify(returnJSON, "/n", null));
            } else {
                let jsonStr = JSON.stringify(returnJSON, "/n", null);
                return jsonStr;
            }
        }
    </script>
</body>

</html>